#!/usr/bin/env python3
#-*- coding: utf-8 -*-

import functools

#log作为fun的装饰器，返回一个wrapper，参数列表应与fun保持一致
#参数是一个可变参数*arg，一个关键字参数**kw
#在wrapper中可以做一些AOP，同时调用fun
def log(fun):
	def wrapper(*arg, **kw):
		print(*arg)
		print(kw)
		print(fun.__name__)
		fun(*arg, **kw)
		print("after_call")
	return wrapper
@log
def test(a,b,c,**kw):
	print("execute test")

test(111,222,333,coding='test')

'''
再思考一下能否写出一个@log的decorator，使它既支持：
@log
def f():
    pass
    
又支持：
@log('execute')
def f():
    pass
'''

def log1(strorfunction):
	if isinstance(strorfunction, str):
		def decorator(fun):
            #把原始函数的__name__等属性复制到wrapper()函数中
			@functools.wraps(fun)
			def wapper(*arg, **kw):
				print("%s %s():" % (strorfunction, fun.__name__))
				return fun(*arg, **kw)
			return wapper
		return decorator
	else:
		@functools.wraps(strorfunction)
		def wapper(*arg, **kw):
			print('%s()' % [strorfunction.__name__])
			strorfunction(*arg, **kw)
		return wapper

@log1
def test1():
	print("execute test1")

@log1('xxx')
def test2():
    print("execute test2")

test1()
test2()
